home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Shareware Grab Bag
/
Shareware Grab Bag.iso
/
007
/
help10.arc
/
HELP.8
next >
Wrap
Text File
|
1987-03-06
|
11KB
|
248 lines
; HELP.COM by Bob Montgomery, 2/23/87
; This program is a generic help screen template for use with the A86
; assembler. The desired help message is written as db's at Hlpst in
; place of the test message that is there now. The only restrictions
; on the help message are:
; 1. The message must not exceed 80 characters wide.
; 2. The message must not exceed 25 lines long.
; 3. Each help line must be the same length.
; The program will auto center the message on the display screen. The hot
; key combo to bring up the help screen is defined as Hotkey below (set
; for Cntl-Leftshift right now) and can be changed to another combination
; by changing the equate for Hotkey.
jmp Init ;Initialize program
Esc equ 1Bh
Vidmem equ 0B800 ;Location of screen 0
Monomem equ 0B000 ;Location of mono screen
BWattr equ 70h ;Grey background, black foreground
; Bits in shift status
Rtsh equ 1
Lftsh equ 2
Cntl equ 4
Alt equ 8
Scrl equ 10h
Numl equ 20h
Capl equ 40h
Mode db ? ;Current video mode
Vpage db ? ;Current video page
Vidseg dw ? ;Current page segment
Hlpflg db 0 ;1 => Help on
Attr db ? ;Attribute to use
Cursor dw ? ;Current cursor type
; ==================================================================
; This is the test help message to be displayed on the video screen.
; Change this area for your own help message, color, and hot key combo.
Colattr equ 4Eh ;Red background, yellow foreground
Hotkey equ Cntl+Lftsh ;Define the hot key combo to bring up screen
Hlpst: db 'AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA'
Linchr equ $-Hlpst ;Chars on each help line
db 'BBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBB'
db 'CCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCC'
db 'DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD'
db 'EEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEE'
DB 'FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF'
db 'GGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGG'
db 'HHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHH'
db 'IIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIII'
db 'JJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJ'
db 'KKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKK'
DB 'LLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLL'
DB 'MMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMM'
DB 'NNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNN'
DB 'OOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOO'
DB 'PPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPP'
DB 'QQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQ'
DB 'RRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRR'
DB 'SSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSS'
DB 'TTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTTT'
DB 'UUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUUU'
DB 'VVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVV'
DB 'WWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWWW'
; ===================================================================
Msglen equ $-Hlpst ;# chars in help buffer
Lines equ Msglen/Linchr ;# lines of help
Buflen equ 2*Msglen ;Screen data buffer length
Stlin equ (25-Lines)/2 ;Start line
Stchr equ (80-Linchr)/2 ;Start byte on line
Stscr equ 160*Stlin + 2*Stchr ;Start of mem to put help
Scrbuf: db Buflen dup (?) ;Buffer for screen data
; New Int 9 routine - check for Cntrl-LShift; ignore others.
; Since Int 9 is called every time a key is pressed or released, and
; reads the keyboard thru some mysterious means in BIOS, we must call
; the old Int 9 as a subroutine each time an Int 9 is generated. But,
; an interrupt routine has a IRET instead of a RET as the return
; instruction, which pops the return address like a RET does, and then
; pops the flags. So to call Int 9 like a subroutine, we have to push
; the flags first; then when the the IRET is executed, control returns
; to our program with the stack pointer at the right place.
Start: push ax,bx,cx,dx,ds,es,di,si ;Save all for calling program
pushf ;Put flags on stack since Int pops flags
Oldint: call 0000:0000 ;Call old Int 9 to get key-will pop flags
mov ah,2 ;Get shift status
Int 16h ;in al
and al,Hotkey ;Only keep Hot keys
cmp al,Hotkey ;Were both pressed?
jne Exit ;No
mov ds,cs ;Yes, set ds=cs
cmp Hlpflg,1 ;Is help already up?
jne Go ;No, put it up
; If help is already up, ignore the Hotkey.
Exit: pop si,di,es,ds,dx,cx,bx,ax ;Restore all for calling program
iret ;Pop return address and flags
; Come here if should put up help.
Go: mov al,Colattr ;Assume color
mov Attr,al
mov ah,15 ;Get video mode in al
int 10h ;and page in bh
mov Mode,al ;Save Mode
mov Vpage,bh ;and page
cmp al,2 ;Mode=2?
je Color ;Yes
cmp al,3 ;Mode=3?
je Color ;Yes
cmp al,7 ;Mode=7? (mono)
jne Exit ;No, must be graphics so exit
mov al,BWattr ;Set B&W attribute
mov Attr,al
mov bx,Monomem ;and start of mono video memory
jmp short A0
Color: mov bl,0 ;Bx=256*display page
add bx,Vidmem ;Get display mem segment
A0: mov ds,bx ;in ds
; Put up help screen.
; First save current screen to buffer.
call Hidecur ;Hide cursor
call Vidoff ;Disable video (avoids snow on CGA)
mov dl,Lines ;Get # lines of help
mov es,cs ;es=cs
mov si,Stscr ;ds:si points to help screen area in disp mem
mov di,Scrbuf ;es:di points to buffer for screen data
push si,es,ds ;Save them
mov ch,0 ;ch=0
mov cl,Linchr ;cx=chars/help line
A1: push si,cx ;Save position in scrn mem & chars/line
cld ;Set to inc si & di
rep movsw ;Move screen to buffer
pop cx,si ;Get start of line & chars/line
add si,160 ;Next line, same column
dec dl ;Done all lines?
jne A1 ;No
; Now put up help.
pop es,ds,di ;Now ds=cs, es:di=help scrn area in screen mem
push di,ds,es ;Put back in orig order
mov si,Hlpst ;Point si to help data
mov dl,Lines ;Get chars/help line
mov ah,Attr ;Get char attribute (color)
B1: push di,cx ;Save disp mem pos & chars/help line
B2: lodsb ;Get a help char in al
stosw ;Save char & attribute in screen mem
loop B2 ;Do whole line
pop cx,di ;Get start of disp line & chars/line
add di,160 ;Next line, same column
dec dl ;Done all lines?
jne B1 ;No
mov Hlpflg,1 ;Yes, indicate help up
call Vidon ;and enable video
; Now, wait for the escape key; come here after each keypress (Int 9).
Wait1: mov ah,0 ;Wait for a key
int 16h
cmp al,Esc ;Was it Escape?
jne Wait1 ;No
; If Esc was pressed, put the old screen back
pop es,ds,di ;ds=cs; es:di=start of help area in disp mem
mov si,Scrbuf ;Point to old screen data buffer
call Vidoff ;Disable video (avoid snow on CGA)
mov dl,Lines ;Chars/help line
C1: push di,cx ;Save scrn mem pointer & chars/line
rep movsw ;Move a line to scrn mem
pop cx,di ;Get start of line & chars/line
add di,160 ;Next line, same column
dec dl ;Done all lines?
jne C1 ;No
mov Hlpflg,0 ;Yes, clear flag
call Vidon ;Enable video
call Showcur ;Turn cursor back on
jmp Exit ;and return
; Sub to turn cursor off; come with ds=video.
Hidecur: push cx,ds
mov ds,cs ;ds=cs
mov ah,3 ;Get current cursor data
mov bh,Vpage ;for current page
int 10h
mov Cursor,cx ;Save cursor type
mov ch,20h ;Set cursor off
mov ah,1
int 10h
pop ds,cx
ret
; Sub to turn cursor on; come with ds=cs.
Showcur: mov cx,Cursor ;Set original cursor Type
mov bh,Vpage
mov ah,1
int 10h
ret
; Turn video off
Vidoff: cs cmp Mode,7 ;Mono?
je D0 ;Yes, skip wait for vert retrace
push ds,dx,ax
call Getmode ;Get current video mode byte
and al,0F7 ;Clear video enable bit
out dx,al ;Send to mode control port
pop ax,dx,ds
D0: ret
; Turn video on
Vidon: cs cmp Mode,7 ;Mono?
je E0 ;Yes, skip wait for vert retrace
push ds,dx,ax
call Getmode ;Get current video mode byte
or al,8 ;Set video enable bit
out dx,al ;Send to mode control port
pop ax,dx,ds
E0: ret
; Sub to wait for vertical retrace to avoid snow on CGA screen.
Vert: mov dx,3DAh ;CRT status port
F1: in al,dx ;Read status
test al,8 ;Vert retrace?
je F1 ;No
mov dx,3D8h ;Point to video mode port
ret ;Yes, return
Getmode: call Vert ;Wait for vert retrace
mov ax,40h ;Get video mode
mov ds,ax ;at 465h
mov al,b[65h]
ret ;and return
; Come here to install the program as the new Int 9 routine.
Init: mov ax,3509h ;Get current Int 9 vector
int 21h ;in es:bx
mov ds,cs ;this code
mov w[Oldint+1],bx ;Save it
mov w[Oldint+3],es
mov ax,2509h ;Set new Int 9 routine
mov dx,Start
int 21h
mov dx,Init ;Terminate and
int 27h ;stay resident